From: George Dunlap Date: Fri, 13 Dec 2019 12:53:04 +0000 (+0000) Subject: x86/mm: Refactor put_page_from_l*e to reduce code duplication X-Git-Tag: archive/raspbian/4.14.0+80-gd101b417b7-1+rpi1^2~63^2~1055 X-Git-Url: https://dgit.raspbian.org/%22http:/www.example.com/cgi/%22https:/%22bookmarks://%22Dat/%22http:/www.example.com/cgi/%22https:/%22bookmarks:/%22Dat?a=commitdiff_plain;h=cca2eac887c64f69b3a7662e2cc6911db097c846;p=xen.git x86/mm: Refactor put_page_from_l*e to reduce code duplication put_page_from_l[234]e have identical functionality for devalidating an entry pointing to a pagetable. But mystifyingly, they duplicate the code in slightly different arrangements that make it hard to tell that it's the same. Create a new function, put_pt_page(), which handles the common functionality; and refactor all the functions to be symmetric, differing only in the level of pagetable expected (and in whether they handle superpages). Other than put_page_from_l2e() gaining an ASSERT it probably should have had already, no functional changes. Signed-off-by: George Dunlap Reviewed-by: Andrew Cooper --- diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c index 97c8d73b7b..59fc820a67 100644 --- a/xen/arch/x86/mm.c +++ b/xen/arch/x86/mm.c @@ -1297,6 +1297,28 @@ static void put_data_page(struct page_info *page, bool writeable) put_page(page); } +static int put_pt_page(struct page_info *pg, struct page_info *ptpg, + unsigned int flags) +{ + int rc = 0; + + if ( flags & PTF_defer ) + { + ASSERT(!(flags & PTF_partial_set)); + current->arch.old_guest_ptpg = ptpg; + current->arch.old_guest_table = pg; + current->arch.old_guest_table_partial = false; + } + else + { + rc = _put_page_type(pg, flags | PTF_preemptible, ptpg); + if ( likely(!rc) ) + put_page(pg); + } + + return rc; +} + /* * NB. Virtual address 'l2e' maps to a machine address within frame 'pfn'. * Note also that this automatically deals correctly with linear p.t.'s. @@ -1304,8 +1326,6 @@ static void put_data_page(struct page_info *page, bool writeable) static int put_page_from_l2e(l2_pgentry_t l2e, unsigned long pfn, unsigned int flags) { - int rc = 0; - if ( !(l2e_get_flags(l2e) & _PAGE_PRESENT) || (l2e_get_pfn(l2e) == pfn) ) return 1; @@ -1319,35 +1339,16 @@ static int put_page_from_l2e(l2_pgentry_t l2e, unsigned long pfn, ((1UL << (L2_PAGETABLE_SHIFT - PAGE_SHIFT)) - 1))); for ( i = 0; i < (1u << PAGETABLE_ORDER); i++, page++ ) put_data_page(page, writeable); - } - else - { - struct page_info *pg = l2e_get_page(l2e); - struct page_info *ptpg = mfn_to_page(_mfn(pfn)); - if ( flags & PTF_defer ) - { - current->arch.old_guest_ptpg = ptpg; - current->arch.old_guest_table = pg; - current->arch.old_guest_table_partial = false; - } - else - { - rc = _put_page_type(pg, flags | PTF_preemptible, ptpg); - if ( likely(!rc) ) - put_page(pg); - } + return 0; } - return rc; + return put_pt_page(l2e_get_page(l2e), mfn_to_page(_mfn(pfn)), flags); } static int put_page_from_l3e(l3_pgentry_t l3e, unsigned long pfn, unsigned int flags) { - struct page_info *pg; - int rc; - if ( !(l3e_get_flags(l3e) & _PAGE_PRESENT) || (l3e_get_pfn(l3e) == pfn) ) return 1; @@ -1365,50 +1366,16 @@ static int put_page_from_l3e(l3_pgentry_t l3e, unsigned long pfn, return 0; } - pg = l3e_get_page(l3e); - - if ( flags & PTF_defer ) - { - ASSERT(!(flags & PTF_partial_set)); - current->arch.old_guest_ptpg = mfn_to_page(_mfn(pfn)); - current->arch.old_guest_table = pg; - current->arch.old_guest_table_partial = false; - return 0; - } - - rc = _put_page_type(pg, flags | PTF_preemptible, mfn_to_page(_mfn(pfn))); - if ( likely(!rc) ) - put_page(pg); - - return rc; + return put_pt_page(l3e_get_page(l3e), mfn_to_page(_mfn(pfn)), flags); } static int put_page_from_l4e(l4_pgentry_t l4e, unsigned long pfn, unsigned int flags) { - int rc = 1; - - if ( (l4e_get_flags(l4e) & _PAGE_PRESENT) && - (l4e_get_pfn(l4e) != pfn) ) - { - struct page_info *pg = l4e_get_page(l4e); - - if ( flags & PTF_defer ) - { - ASSERT(!(flags & PTF_partial_set)); - current->arch.old_guest_ptpg = mfn_to_page(_mfn(pfn)); - current->arch.old_guest_table = pg; - current->arch.old_guest_table_partial = false; - return 0; - } - - rc = _put_page_type(pg, flags | PTF_preemptible, - mfn_to_page(_mfn(pfn))); - if ( likely(!rc) ) - put_page(pg); - } + if ( !(l4e_get_flags(l4e) & _PAGE_PRESENT) || (l4e_get_pfn(l4e) == pfn) ) + return 1; - return rc; + return put_pt_page(l4e_get_page(l4e), mfn_to_page(_mfn(pfn)), flags); } static int alloc_l1_table(struct page_info *page)